use "./OutputInterim/All_Rates_Dates_Basis_Returns.dta", clear
 

 //don't list USD in these
local ois_1M_currencies JPY AUD EUR CAD GBP  
local ois_3M_currencies `ois_1M_currencies'

local ibor_1M_currencies JPY AUD EUR GBP CHF // CAD missing data, maybe not much to do about it
local ibor_3M_currencies JPY AUD EUR GBP CHF //CAD could have been used, but wanted to parallel 1M horizon


local ois_top6 AUD_JPY AUD_EUR USD_JPY CAD_JPY USD_EUR GBP_JPY

//actually 8
local ibor_top6 AUD_JPY AUD_EUR AUD_CHF USD_JPY USD_EUR USD_CHF AUD_GBP GBP_JPY 

format Date %td
gen post_crisis = Date >= mdy(7,1,2010) & Date <= mdy(12,31,2020)


keep Date *USD_ois_spot_log_basis_3M *USD_ois_log_return_1M_fwd_3M *USD_ois_log_return_3M_fwd_3M *USD_ois_log_return_1M_fwd_1M *USD_ibor_log_ret_1M_fwd_3M *USD_ibor_log_ret_3M_fwd_3M post_crisis

//remove log to shorten names
rename *ois_log_return* *ois_log_ret*
//rename *ibor_log_return* *ibor_log_ret*

foreach rate in ois ibor {

	foreach horizon in 1M 3M {
		
		local tenors 3M
		
		if "`horizon'" == "1M" & "`rate'" == "ois" {
			local tenors 3M 1M
		}
		
		foreach tenor in `tenors' {
			
			foreach ccy in ``rate'_`horizon'_currencies' {
	
				foreach ccy2 in ``rate'_`horizon'_currencies' {
					if "`ccy'" ~= "`ccy2'" {
						gen ret_`ccy'_`ccy2' = `ccy'_USD_`rate'_log_ret_`horizon'_fwd_`tenor' - `ccy2'_USD_`rate'_log_ret_`horizon'_fwd_`tenor'
					}
				}		
			}
			
			foreach ccy in ``rate'_`horizon'_currencies' {
				gen ret_`ccy'_USD = `ccy'_USD_`rate'_log_ret_`horizon'_fwd_`tenor'
				gen ret_USD_`ccy' = -`ccy'_USD_`rate'_log_ret_`horizon'_fwd_`tenor'
			}
			
			foreach pair in ``rate'_top6' {
				
				gen pret_`pair' = ret_`pair'
			}
			
			su ret_*_USD if post_crisis
			
			pca ret_* if post_crisis, com(1) cov
			predict pc1ret //if post_crisis
			
			pca pret_* if post_crisis, com(1) cov
			predict pc1top6 //if post_crisis
			
			matrix wts_top6 = e(L)
			
			//standardize to have positive correlation and same SD as AUD_JPY
			//code will fail if covariance happens to be zero, not a problem in our case

			corr pc1ret ret_AUD_JPY if post_crisis & pc1ret != . & ret_AUD_JPY != ., cov

			local retcov = r(cov_12)
			local varret = r(Var_1)
			local varaudjpy = r(Var_2)

			gen pc1ret_stand = pc1ret / sqrt(`varret' / `varaudjpy') * `retcov' / abs(`retcov')
			
			corr pc1top6 ret_AUD_JPY if post_crisis, cov

			local retcov = r(cov_12)
			local varret = r(Var_1)
			local varaudjpy = r(Var_2)

			gen pc1top6_stand = pc1top6 / sqrt(`varret' / `varaudjpy') * `retcov' / abs(`retcov')

			matrix wts_top6 = wts_top6 / sqrt(`varret' / `varaudjpy') * `retcov' / abs(`retcov')
			
			matrix list wts_top6
			
			su pc1top6 ret_AUD_JPY pc1top6_stand if post_crisis
			
			corr ret_AUD_JPY pc1ret_stand pc1top6_stand if post_crisis
			
			drop pc1ret ret_* pret_* pc1top6
			rename pc1ret_stand pc1ret_`rate'_stand_`horizon'_fwd_`tenor'
			rename pc1top6_stand pc1top6_`rate'_stand_`horizon'_fwd_`tenor'
		}
		
	}

}


keep Date pc1ret_* pc1top6_*

save "./OutputInterim/PCports.dta", replace

outsheet using "./OutputInterim/PCports.csv", comma replace

gen month = mofd(Date)
sort Date
	
collapse (lastnm) pc1ret* pc1top6*, by(month)

rename month Date
format Date %tm
sort Date

save "./OutputInterim/PCportsMonthly.dta", replace

outsheet using "./OutputInterim/PCportsMonthly.csv", comma replace


//old code below to compute PCA based on basis values
//generates virtually identical results


/*pca basis_* if post_crisis, com(1) cov

matrix temp = e(L)

gen pc1basis = 0

foreach ccy in `currencies' USD {
	
		foreach ccy2 in `currencies' USD {
				if "`ccy'" ~= "`ccy2'" {
					local coeff = temp["basis_`ccy'_`ccy2'",1]
					disp "coeff: `coeff'"
					replace pc1basis = pc1basis + `coeff'*ret_`ccy'_`ccy2'
				}
		}
}
*/



/*corr pc1basis ret_AUD_JPY if post_crisis, cov

local basiscov = r(cov_12)
local varbasis = r(Var_1)
local varaudjpy = r(Var_2)

gen pc1basis_stand = pc1basis / sqrt(`varbasis' / `varaudjpy') * `basiscov' / abs(`basiscov')

su ret_AUD_JPY pc1ret_stand pc1basis_stand if post_crisis*/


